package sfsoftware.game.actor.enemy;

import sfsoftware.game.trevor.Player;
import sfsoftware.game.trevor.ui.Dialog;
import sfsoftware.util.Actor;
import sfsoftware.util.Tile;

public class SmartBullet extends Bullet {
	private boolean collidable = true;
	private double directionAngle;
	
	public SmartBullet(int destX, int destY, String texture, int destWidth, int destHeight, Tile[][] assocTileMap) {
		super(destX, destY, texture, destWidth, destHeight, assocTileMap);
		directionAngle = getAngleToPlayer();
	}

	public SmartBullet(int destX, int destY, String texture, int destWidth, int destHeight, Tile[][] assocTileMap, int bulletDamage) {
		super(destX, destY, texture, destWidth, destHeight, assocTileMap, bulletDamage);
		directionAngle = getAngleToPlayer();
	}
	
	public SmartBullet(int destX, int destY, String texture, int destWidth, int destHeight, Tile[][] assocTileMap, int bulletDamage, double destAngle) {
		super(destX, destY, texture, destWidth, destHeight, assocTileMap, bulletDamage);
		directionAngle = destAngle;
	}
	
	public SmartBullet(int destX, int destY, String texture, int srcX, int srcY, int destWidth, int destHeight, Tile[][] assocTileMap) {
		super(destX, destY, texture, srcX, srcY, destWidth, destHeight,	assocTileMap);
		directionAngle = getAngleToPlayer();
	}
	
	public SmartBullet(int destX, int destY, String texture, int srcX, int srcY, int destWidth, int destHeight, Tile[][] assocTileMap, int bulletDamage) {
		super(destX, destY, texture, srcX, srcY, destWidth, destHeight,	assocTileMap, bulletDamage);
		directionAngle = getAngleToPlayer();
	}	

	public SmartBullet(int destX, int destY, String texture, int srcX, int srcY, int destWidth, int destHeight, Tile[][] assocTileMap, int bulletDamage, double destAngle) {
		super(destX, destY, texture, srcX, srcY, destWidth, destHeight,	assocTileMap, bulletDamage);
		directionAngle = destAngle;
	}
	
	private double getAngleToPlayer()
	{
		double dx = (getX() + (getWidth() / 2)) - (Player.getXPos() + 20);
		double dy = (getY() + (getHeight() / 2)) - (Player.getYPos() + 20);
		double inRads = Math.atan2(dy,dx);
		
		if (inRads < 0)
		{
	        inRads = Math.abs(inRads);
		}
	    else
	    {
	        inRads = 2 * Math.PI - inRads;
	    }			
		
		return inRads;
	}
	
	@Override
	public boolean move(double dirX, double dirY, Tile[][] tileMap)
	{			
		boolean successfulMove = false;
		if(!(sfsoftware.game.TrevorLegacy.isPaused) && !(Dialog.displayDialog))
		{
			
			int x = (int) (this.getX() + (width / 2));
			int y = (int) (this.getY() + (height / 2));
			
			int xTile = (int) Math.floor(((x - playingFieldX) / 40));
			int yTile = (int) Math.floor(((y - playingFieldY) / 40));													
			
			if(!(collidingWithCast(dirX, dirY)))
			{				
				updateCornerVariables(x, (int) (y + Math.round((speed * dirY))), tileMap);
				if(dirY < 0)
				{
					if(topLeft && topRight)
					{
						super.move(this.getX(), (float) (this.getY() + (dirY * speed)));
						successfulMove = true;
					}
					else
					{				
						super.move(this.getX(), playingFieldY + (yTile * 40));
						return false;
					}
				}
				if(dirY > 0)
				{
					if(bottomLeft && bottomRight)
					{
						super.move(this.getX(), (float) (this.getY() + (dirY * speed)));
						successfulMove = true;
					}
					else
					{
						super.move(this.getX(), playingFieldY + (yTile * 40) + (40 - height));
						return false;
					}			
				}
				updateCornerVariables((int) (x + Math.round((speed * dirX))), y, tileMap);		 
				if(dirX < 0)
				{
					if(topLeft && bottomLeft)
					{
						super.move((float) (this.getX() + (dirX * speed)), this.getY());
						successfulMove = true;
					}
					else
					{
						super.move(playingFieldX + (xTile * 40), this.getY());		
						return false;
					}
				}
				if(dirX > 0)
				{
					if(topRight && bottomRight)
					{
						super.move((float) (this.getX() + (dirX * speed)), this.getY());
						successfulMove = true;
					}
					else
					{
						super.move(playingFieldX + (xTile * 40) + (40 - width), this.getY());
						return false;
					}			
				}
			}
		}
		return successfulMove;
	}
	
	public void setCollidable(boolean newValue)
	{
		collidable = newValue;
	}
	
	@Override
	public void update() 
	{
		double xDirection = Math.cos(directionAngle) * -1;
		double yDirection = Math.sin(directionAngle);		
		
		try
		{
			if(collidable)
			{
				if(!(move(xDirection, yDirection, tileMap)))
				{				
					Actor.cast.remove(this);
					generateParticles(40, 0.75f, 0, 0);
				}
			}
			else
			{
				super.moveWithoutCheckingCollision(xDirection, yDirection);
				// If the bullet is off the screen, remove it!
				if(getX() > 640 || (getX() + getWidth()) < 0 || getY() > 480 || (getY() + getHeight()) < 0)
				{
					Actor.cast.remove(this);
				}
			}
		}
		catch(ArrayIndexOutOfBoundsException e)
		{
			Actor.cast.remove(this);
			generateParticles(40, 0.75f, 0, 0);
		}
	}
	
	@Override
	public void wiffaHit() 
	{
	
	}
	
}
